/*
* File: CLogger.cpp
* Copyright (c) 2010. Silviu Caragea <silviu@intelliproject.net>
* Created on Aug 23, 2010, 11:14 PM
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*  1.Redistributions of source code must retain the above copyright
*    notice, this list of conditions and the following disclaimer.
*  2.Redistributions in binary form must reproduce the above copyright
*    notice, this list of conditions and the following disclaimer in the
*    documentation and/or other materials provided with the distribution.
*  3.All advertising materials mentioning features or use of this software
*    must display the following acknowledgement:
*       This product includes software developed by the University of
*       California, Berkeley and its contributors.
*  4.Neither the name of the University nor the names of its contributors
*    may be used to endorse or promote products derived from this software
*    without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS''
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED.IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
* IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
* OF THE POSSIBILITY OF SUCH DAMAGE.
*/

#include "CLogger.h"
#include "basic_types.h"

namespace litevent{
namespace util{

CLogger* CLogger::m_pInstance = NULL;

CLogger* CLogger::sharedLogger()
{
    if (m_pInstance == NULL)
        m_pInstance = new CLogger();

    return m_pInstance;
}

CLogger::CLogger()
{
#ifndef HAVE_CONSOLE_LOGGER
    this->fd = -1;
#endif

    this->m_bLogging = true;
    msgBuffer = (char*) malloc(LOGGER_BUFFER_SIZE * sizeof (char));
}

CLogger::~CLogger()
{
    this->closeLog();

    if (msgBuffer)
        free(msgBuffer);
}

bool CLogger::openLog(const char* szFilePath, bool bLogging)
{
    bool returnValue = true;

    m_crtSection.lock();

    this->m_bLogging = bLogging;

#ifndef HAVE_CONSOLE_LOGGER

#ifdef WIN32	
    if (-1 == (fd = _open(szFilePath, O_APPEND | O_WRONLY | O_CREAT)))
#else
	if (-1 == (fd = open(szFilePath, O_APPEND | O_WRONLY | O_CREAT | O_LARGEFILE, 0644)))
#endif
    {
        printf("[%s %d] opening errorlog '%s' failed:%s", __FILE__, __LINE__, szFilePath, strerror(errno));
        returnValue = false;
    }
#else
    UNUSED(szFilePath);
#endif

    m_crtSection.unlock();

    return returnValue;
}

//write formated text

void CLogger::WriteFormated(const char* szFormat, ...)
{
    va_list valist;
    va_start(valist, szFormat);
    char szMsg[1024];
    vsprintf(szMsg, szFormat, valist);
    va_end(valist);
    this->Write(szMsg);
}

//write string

void CLogger::Write(const char* szText)
{
    m_crtSection.lock();

#ifndef HAVE_CONSOLE_LOGGER
    if (m_bLogging && fd != -1)
#else
    if (m_bLogging)
#endif
    {
        char szDateTime[255];
        time_t tm;

#ifndef WIN32
        strftime(szDateTime, 255, "%Y-%m-%d %H:%M:%S", localtime(&tm));
#else
		char szTime[128],szDate[128];
		_strtime(szTime);
		_strdate(szDate);
		sprintf(szDateTime, "%s %s", szDate, szTime);
#endif

#ifdef HAVE_CONSOLE_LOGGER
        //fprintf(stdout, "[%s] %s\n", szDateTime, szText);
        sprintf(msgBuffer, "[%s] %s\n", szDateTime, szText);
        printf("%s", msgBuffer);
#else
        sprintf(msgBuffer, "[%s] %s\n", szDateTime, szText);

#ifdef WIN32
		_write(fd, msgBuffer, strlen(msgBuffer));
#else
        write(fd, msgBuffer, strlen(msgBuffer));
#endif

#endif

    }

    m_crtSection.unlock();

}

}}
